module AboutYou
  module SDK
    module Model
      ###
      # BasketItem is a class used for adding a variant item into the basket
      #
      # If you want to add a variant into a basket, you need to create an instance
      # of a BasketItem. The BasketItem represents a variant by it's variant_id.
      # It can contain $additional_data that will be transmitted to the merchant untouched.
      ###
      class BasketItem
        include AboutYou::SDK::Model::ResultError
        include AboutYou::SDK::Model::AbstractBasketItem
        include AboutYou::SDK::Model::BasketVariantItem

        # The ID of this basket item. You can choose this ID by yourself to identify your item later.
        attr_accessor :id

        ###
        # Constructor for the AboutYou::SDK::Model::BasketItem class
        #
        # * *Args*    :
        #   - +id+ -> the basket item id
        #   - +variant_id+ -> the id of the variant
        #   - +additional_data+ -> additional data of the basket item [optional]
        #   - +app_id+ -> the app id [optional]
        #
        # * *Returns* :
        #   - an instance of AboutYou::SDK::Model::BasketItem
        ###
        def initialize(id, variant_id, additional_data = nil, app_id = nil)
          check_id(id)
          self.id = id
          super(variant_id, additional_data, app_id)

          self
        end

        ###
        # This method is used for creating a basket item with a given api json
        # response. It is best practice to use this method.
        #
        # * *Args*    :
        #   - +json_object+ -> the api response key
        #   - +products+ -> array of products
        #
        # * *Returns* :
        #   - an instance of AboutYou::SDK::Model::BasketItem
        ###
        def create_from_json(json_object, products)
          item = new(
              json_object['id'],
              json_object['variant_id'],
              if json_object.key?('additional_data')
                [json_object['additional_data']]
              else
                nil
              end,
              json_object.key?('app_id') ? json_object['app_id'] : nil
          )

          item.parse_error_result(json_object)
          item.json_object = json_object

          unless json_object['product_id'].empty?
            if products.key?(json_object['product_id'])
              item.product = products[json_object['product_id']]
            else
              fail 'UnexpectedResultException! Product with ID ' +
                String(json_object['product_id']) +
                ' expected but wasnt received with the basket'
            end
          end

          item
        end

        ###
        # This method checks whether an basket item id is valid or not
        #
        # * *Args*    :
        #   - +id+ -> the id which should be checked
        #
        # * *Fails* :
        #   - if the id is not a String and has less then 2 characters
        ###
        def check_id(id)
          fail '\InvalidArgumentException! ID of the BasketSetItem must be
            a String that must contain minimum two characters' unless
            id.is_a?(String) && id.length < 2
        end
      end
    end
  end
end
